/*
* INSANE - Interactive Structural Analysis Environment
*
* Copyright (C) 2003-2005
* Universidade Federal de Minas Gerais
* Escola de Engenharia
* Departamento de Engenharia de Estruturas
* 
* Author's email :    insane@dees.ufmg.br
* Author's website :  http://www.dees.ufmg.br/insane
* 
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or any later version.
* 
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
* GNU General Public License for more details.
* 
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
*/
package br.ufmg.dees.insane.analysisModel;

import java.util.ArrayList;

import br.ufmg.dees.insane.util.IMatrix;
import br.ufmg.dees.insane.util.IVector;
import br.ufmg.dees.insane.util.geometricProperties.GeometricProperties;
import br.ufmg.dees.insane.util.pointValues.PointValues;
import br.ufmg.dees.insane.util.pointValues.StringPointValues;


/** A class representing a PolarPlaneStrain
 * @author jamile
 * 17/11/2005
 */
public abstract class PolarPlane implements AnalysisModel {
	
	    /**Constructs a Polar Plane Analysis Model.*/
	    public PolarPlane()
	    {
	    }
	    
	    /** Return the jacobian matrix.
		*@param dl The matrix of local derivates.
		*@param cN The matrix of nodal coordinates.
		*@return dl * cN The jacobian matrix.
		*/
	    protected IMatrix getJacobian(IMatrix dl, IMatrix cN)
		{
			IMatrix jacobian = new IMatrix(this.getDominion(),this.getDominion());
			jacobian.setZero();
			jacobian.mul(dl, cN);
			return(jacobian);
		}
	    
	    /** Return the inverse of jacobian matrix.
	    *@param a The jacobian matrix.
	    *@return the inverse of jacobian matrix.
	    */
	    protected IMatrix invertJacobian(IMatrix a)
	    {
	        IMatrix b = new IMatrix(2,2);
	        b.setZero();
	        b.setElement(0,0,a.getElement(1,1));
	        b.setElement(0,1,((-1)*(a.getElement(1,0))));
	        b.setElement(1,0,((-1)*(a.getElement(0,1))));
	        b.setElement(1,1,a.getElement(0,0));
	        b.transpose();
	        b.setScale(1/a.determinantLU());
	        return (b);
	    }
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getShapeMatrix(br.ufmg.dees.insane.util.IVector)
	     */
	    public IMatrix getStateVariableOperator(IMatrix d, IVector n, IMatrix c) {
	        IMatrix matrixN = new IMatrix(3,(3*(n.getSize())));
	        matrixN.setZero();
	        for(int i = 0; i < (n.getSize()); i++)
	        {
	            for(int j = 0; j < 3; j++)
	            {
	                matrixN.setElement( j, (3*i)+j, (n.getElement(i)));
	            }
	        }
	        return matrixN;
	    }
	    
	    /* (non-Javadoc)
		 * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getGeometricOperator(br.ufmg.dees.insane.util.IVector)
		 */
	    public IMatrix getGeometricOperator(IVector n1) {    	
	    	IMatrix matrixN = new IMatrix(2,(2*(n1.getSize())));
	        matrixN.setZero();
	        for(int i = 0; i < (n1.getSize()); i++)
	        {
	            for(int j = 0; j < 2; j++)
	            {
	                matrixN.setElement( j, (2*i)+j, (n1.getElement(i)));
	            }
	        }
	        return matrixN;
	    }
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getDominion()
	     */
	    public int getDominion() {
	        return 2;
	    }	    
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getIntegrationFactor(br.ufmg.dees.insane.util.IVector, br.ufmg.dees.insane.util.IMatrix)
	     */
	    public double getIntegrationFactor(IVector n, IMatrix cN, GeometricProperties gps) {
//	    	GeometricProperties gp = new GeometricProperties(mps);
//	    	return gp.getThickness();
	    	return 1.0;
	    }
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getJacobianTransformation(br.ufmg.dees.insane.util.IMatrix, br.ufmg.dees.insane.util.IMatrix)
	     */
	    public double getJacobianTransformation(IMatrix dl, IMatrix cN) {
	    	IMatrix jacobian = new IMatrix(this.getDominion(),this.getDominion());
	        jacobian.setZero();
	        jacobian.mul(dl, cN);
	        double detJ = jacobian.determinantLU();
	        return(detJ);
	    }
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getTransformationMatrix(br.ufmg.dees.insane.util.IMatrix, br.ufmg.dees.insane.util.IMatrix)
	     */
	    public IMatrix getTransformationMatrix(IMatrix dl, IMatrix cN) {
	    	IMatrix transf = new IMatrix(dl.getNumCol()*3,dl.getNumCol()*3);
	    	transf.setIdentity();
	        return transf;
	    } 
	    
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getDOFLabels(int)
	     */
	    public ArrayList getDOFLabels(int n){
			ArrayList <PointValues> al = new ArrayList<PointValues>();
			PointValues spv = new StringPointValues();
		    spv.addPointValue("Dx");
		    spv.addPointValue("Dy");
		    spv.addPointValue("MRz");
			for(int i=0; i<n; i++) {
				al.add(i,spv);
			}
			return al;
		}
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getDOFLabels(int)
	     */
	    public ArrayList getDOFLabels(){
			ArrayList <String> al = new ArrayList<String>();
			al.add("Dx");
			al.add("Dy");
			al.add("MRz");
			return al;
		}
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getType()
	     */	    
	    public abstract String getLabel();
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getDualInternalVariableOperator(br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract IMatrix getDualInternalVariableOperator(IMatrix e);

	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getDualInternalVariableOperator(br.ufmg.dees.insane.util.IMatrix)
	     */
		public IMatrix modifyDualInternalVariableOperator(IMatrix e, GeometricProperties gps){
			e.setScale(gps.getThickness());
			return e;
		}
		
		/* (non-Javadoc)
		 * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#modifyDualInternalVariableVector(br.ufmg.dees.insane.util.IVector, br.ufmg.dees.insane.util.geometricProperties.GeometricProperties)
		 */
		public IVector modifyDualInternalVariableVector(IVector s, GeometricProperties gps) {
			s.scale(gps.getThickness());
			return s;
		}
		
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getNumberOfInternalVariables()
	     */
	    public abstract int getNumberOfInternalVariables();

	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getNumberOfDualInternalVariables()
	     */
	    public abstract int getNumberOfDualInternalVariables();

	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getInternalVariablesTensor(br.ufmg.dees.insane.util.IVector, br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract IMatrix getInternalVariablesTensor(IVector a, IMatrix b);

	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getInternalDualVariablesTensor(br.ufmg.dees.insane.util.IVector, br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract IMatrix getDualInternalVariablesTensor(IVector a, IMatrix b);

	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getInternalVariablesDirLabels()
	     */
	    public abstract String[] getInternalVariablesLabels();

	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getInternalDualVariablesDirLabels()
	     */
	    public abstract String[] getDualInternalVariablesLabels();

	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#expandVector(br.ufmg.dees.insane.util.IVector)
	     */
	    public abstract IVector expandVector(IVector a);

	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#expandTensor(br.ufmg.dees.insane.util.IVector)
	     */
	    public abstract IMatrix expandTensor(IVector a);

	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#reduceVector(br.ufmg.dees.insane.util.IVector)
	     */
	    public abstract IVector reduceVector(IVector a);
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#reduceTensor(br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract IVector reduceTensor(IMatrix a);	        
	       
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getJ2(br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract double getJ2(IVector s);
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getdJ2dSIG(br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract IVector getdJ2dSIG (IVector s);
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getJ3(br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract double getJ3(IVector s);
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getdJ3dSIG(br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract IVector getdJ3dSIG (IVector s);
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getI1(br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract double getI1(IVector s);
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getdI1dSIG(br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract IVector getdI1dSIG (IVector s);
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getI2(br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract double getI2(IVector s);
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getdI2dSIG(br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract IVector getdI2dSIG (IVector s);
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getI3(br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract double getI3(IVector s);
	    
	    /* (non-Javadoc)
	     * @see br.ufmg.dees.insane.analysisModel.AnalysisModel#getdI3dSIG(br.ufmg.dees.insane.util.IMatrix)
	     */
	    public abstract IVector getdI3dSIG (IVector s);
    
   }
